/*
 *  MTouchware_senders.c
 *
 *  This code monitors handles sending the messages to other applications.
 *
 *  Copyright (C) 2010 LIMSI-CNRS (Orsay-France) and EFREI (Paris-France)
 *
 *  Authors: Rami Ajaj, Nicolas Flasque and Frederic Vernier.
 *
 *  This program is free software; you can redistribute it and/or modify
 *  it under the terms of the GNU Lesser General Public License as
 *  published by the Free Software Foundation; either version 2.1 of the
 *  License, or (at your option) any later version.
 *
 *  This program is distributed in the hope that it will be useful,
 *  but WITHOUT ANY WARRANTY; without even the implied warranty of
 *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 *  GNU Lesser General Public License for more details.
 *
 *  $Id$
 */

#include "MTouchware_senders.h"

lo_address *MTouchware_senders=NULL;
int nb_MTouchware_senders=0;

void create_MTouchware_senders(char* adress_out, char* port_out) {
  MTouchware_senders = malloc(sizeof(lo_address));
  if (NULL != MTouchware_senders){
    MTouchware_senders[0] = lo_address_new(adress_out, port_out);
    nb_MTouchware_senders = 1;
  }
}

void delete_MTouchware_senders() {
  //free(MTouchware_senders);
  MTouchware_senders=NULL;
  nb_MTouchware_senders=0;
}

int add_MTouchware_sender(char* adress_out, char* port_out) {
  lo_address* tmp = realloc(MTouchware_senders,sizeof(lo_address)*(nb_MTouchware_senders));
  if (tmp != NULL) {
    MTouchware_senders = tmp; /* OK, assign new, larger storage to p */
  }
  if (NULL != MTouchware_senders) {
    MTouchware_senders[nb_MTouchware_senders] = lo_address_new(adress_out, port_out);
    nb_MTouchware_senders++;
    return 0;
  }
  return 1;
}

//send_message_lo_args calls send_message with the appropriate set of arguments
//called when the number of arguments is unknown (e.g. TUIO alive message)

void send_message_lo_args(const char *path, const char *types, lo_arg **argv)
{
	switch ( strlen(types) ) {
		case 0:
			send_message(path , types,NULL);
			break;
		case 1:
			send_message(path,types,&argv[0]->s);
			break;
		case 2:
			send_message(path,types,&argv[0]->s,argv[1]->i);
			break;
		case 3:
			send_message(path,types,&argv[0]->s,argv[1]->i,argv[2]->i);
			break;
		case 4:
			send_message(path,types,&argv[0]->s,argv[1]->i,argv[2]->i,argv[3]->i);
			break;
		case 5:
			send_message(path,types,&argv[0]->s,argv[1]->i,argv[2]->i,argv[3]->i,argv[4]->i);
			break;
		case 6:
			send_message(path,types,&argv[0]->s,argv[1]->i,argv[2]->i,argv[3]->i,argv[4]->i,argv[5]->i);
			break;
		case 7:
			send_message(path,types,&argv[0]->s,argv[1]->i,argv[2]->i,argv[3]->i,argv[4]->i,argv[5]->i,argv[6]->i);
			break;
		case 8:
			send_message(path,types,&argv[0]->s,argv[1]->i,argv[2]->i,argv[3]->i,argv[4]->i,argv[5]->i,argv[6]->i,argv[7]->i);
			break;
		case 9:
			send_message(path,types,&argv[0]->s,argv[1]->i,argv[2]->i,argv[3]->i,argv[4]->i,argv[5]->i,argv[6]->i,argv[7]->i,argv[8]->i);
			break;
		case 10:
			send_message(path,types,&argv[0]->s,argv[1]->i,argv[2]->i,argv[3]->i,argv[4]->i,argv[5]->i,argv[6]->i,argv[7]->i,argv[8]->i,argv[9]->i);
			break;
		case 11:
			send_message(path,types,&argv[0]->s,argv[1]->i,argv[2]->i,argv[3]->i,argv[4]->i,argv[5]->i,argv[6]->i,argv[7]->i,argv[8]->i,argv[9]->i,argv[10]->i);
			break;
		case 12:
			send_message(path,types,&argv[0]->s,argv[1]->i,argv[2]->i,argv[3]->i,argv[4]->i,argv[5]->i,argv[6]->i,argv[7]->i,argv[8]->i,argv[9]->i,argv[10]->i,argv[11]->i);
			break;
		case 13:
			send_message(path,types,&argv[0]->s,argv[1]->i,argv[2]->i,argv[3]->i,argv[4]->i,argv[5]->i,argv[6]->i,argv[7]->i,argv[8]->i,argv[9]->i,argv[10]->i,argv[11]->i,argv[12]->i);
			break;
		case 14:
			send_message(path,types,&argv[0]->s,argv[1]->i,argv[2]->i,argv[3]->i,argv[4]->i,argv[5]->i,argv[6]->i,argv[7]->i,argv[8]->i,argv[9]->i,argv[10]->i,argv[11]->i,argv[12]->i,argv[13]->i);
			break;
		case 15:
			send_message(path,types,&argv[0]->s,argv[1]->i,argv[2]->i,argv[3]->i,argv[4]->i,argv[5]->i,argv[6]->i,argv[7]->i,argv[8]->i,argv[9]->i,argv[10]->i,argv[11]->i,argv[12]->i,argv[13]->i,argv[14]->i);
			break;
		case 16:
			send_message(path,types,&argv[0]->s,argv[1]->i,argv[2]->i,argv[3]->i,argv[4]->i,argv[5]->i,argv[6]->i,argv[7]->i,argv[8]->i,argv[9]->i,argv[10]->i,argv[11]->i,argv[12]->i,argv[13]->i,argv[14]->i,argv[15]->i);
			break;
		case 17:
			send_message(path,types,&argv[0]->s,argv[1]->i,argv[2]->i,argv[3]->i,argv[4]->i,argv[5]->i,argv[6]->i,argv[7]->i,argv[8]->i,argv[9]->i,argv[10]->i,argv[11]->i,argv[12]->i,argv[13]->i,argv[14]->i,argv[15]->i,argv[16]->i);
			break;
		case 18:
			send_message(path,types,&argv[0]->s,argv[1]->i,argv[2]->i,argv[3]->i,argv[4]->i,argv[5]->i,argv[6]->i,argv[7]->i,argv[8]->i,argv[9]->i,argv[10]->i,argv[11]->i,argv[12]->i,argv[13]->i,argv[14]->i,argv[15]->i,argv[16]->i,argv[17]->i);
			break;
		case 19:
			send_message(path,types,&argv[0]->s,argv[1]->i,argv[2]->i,argv[3]->i,argv[4]->i,argv[5]->i,argv[6]->i,argv[7]->i,argv[8]->i,argv[9]->i,argv[10]->i,argv[11]->i,argv[12]->i,argv[13]->i,argv[14]->i,argv[15]->i,argv[16]->i,argv[17]->i,argv[18]->i);
			break;
		case 20:
			send_message(path,types,&argv[0]->s,argv[1]->i,argv[2]->i,argv[3]->i,argv[4]->i,argv[5]->i,argv[6]->i,argv[7]->i,argv[8]->i,argv[9]->i,argv[10]->i,argv[11]->i,argv[12]->i,argv[13]->i,argv[14]->i,argv[15]->i,argv[16]->i,argv[17]->i,argv[18]->i,argv[19]->i);
			break;
		default:
      break;
  }
}

// This is done in a macro because of lo_send variadic function
/*void send_message(const char *path, const char *types, ...){
 int i;
 //va_list vl;
 //va_start( vl, types );
 for (i=0; i<nb_MTouchware_senders; i++) {
 
 //char *outport = lo_address_get_port(MTouchware_senders[i]);
 //printf("%d : sending message on port %s \n", i, outport);
 if (lo_send(MTouchware_senders[i], path, types, __VA_ARGS__ ) == -1) {
 //if (lo_send(MTouchware_senders[i], "/foo/bar", "ffi", 0.12345678f, 23.0f, i) == -1) {
 printf("OSC error %d: %s\n", lo_address_errno(MTouchware_senders[i]), lo_address_errstr(MTouchware_senders[i]));
 }
 //va_end(vl);
 }
 }*/
